﻿using System;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
using MineSweeping.AppCode;
using MineSweeping.AppCode.Tops;

namespace MineSweeping
{
    public partial class MainPage
    {
        private readonly GameContext context = App.Context;

        private const int blockEdge = 56;

        private Block[,] blockMatrix;

        public MainPage()
        {
            InitializeComponent();

            this.LayoutRoot.DataContext = context;
        }

        private void StartBtn_Click(object sender, RoutedEventArgs e)
        {
            // Popup a dialog
            popStartGame.IsOpen =true;
        }

        private void btnStartGame_Click(object sender, RoutedEventArgs e)
        {
            this.Dispatcher.BeginInvoke(
                () =>
                    {
                        Difficulty diff = Difficulty.Easy;
                        
                        if (radioMedium.IsChecked == true)
                        {
                            diff = Difficulty.Medium;
                        }
                        if (radioHard.IsChecked == true)
                        {
                            diff = Difficulty.Hard;
                        }

                        context.InitGameContext(diff);

                        InitGameLayout();

                        popStartGame.IsOpen = false;

                        context.StartTimer();
                    }
                );
        }

        private void btnCancelGame_Click(object sender, RoutedEventArgs e)
        {
            popStartGame.IsOpen = false;
        }

        private void BtnNavToTops_Click(object sender, RoutedEventArgs e)
        {
            NavigationService.Navigate(new Uri("/TopsPage.xaml", UriKind.Relative));
        }

        private void RecordBtn_Click(object sender, RoutedEventArgs e)
        {
            NavigationService.Navigate(new Uri("/TopsPage.xaml", UriKind.Relative));
        }

        private void InitGameLayout()
        {
            GameCanvas.Children.Clear();

            context.IsFlaging = false;

            blockMatrix = new Block[context.Rows + 2, context.Cols + 2];

            GameCanvas.Height = blockEdge * context.Rows;
            GameCanvas.Width = blockEdge * context.Cols;

            var mineMatrix = MineMatrix.InitMines(context.MineCount, context.Rows, context.Cols);

            for (var c = 1; c <= context.Cols; c++)
            {
                for (var r = 1; r <= context.Rows; r++)
                {
                    var block = new Block(r, c, blockEdge, mineMatrix[r, c]);
                    block.SetValue(Canvas.LeftProperty, (double)(c - 1) * blockEdge);
                    block.SetValue(Canvas.TopProperty, (double)(r - 1) * blockEdge);
                    block.Tap += block_Tap;
                    GameCanvas.Children.Add(block);
                    blockMatrix[r, c] = block;
                }
            }
        }

        private void block_Tap(object sender, GestureEventArgs e)
        {
            this.Dispatcher.BeginInvoke(
                () =>
                {
                    var block = sender as Block;

                    if (block == null){return;}

                    if (block.Showed){return;}

                    if (context.IsFlaging)
                    {
                        context.MineLeftCount += block.SetFlag();
                        return;
                    }

                    if (block.Flaged){return;}

                    block.Showed = true;

                    var value = blockMatrix[block.Row, block.Column].MineValue;
                    block.SetShowed(value);

                    // 连翻条件
                    if (value == 0)
                    {
                        block_Tap( blockMatrix[block.Row - 1, block.Column - 1], e);
                        block_Tap(blockMatrix[block.Row - 1, block.Column], e);
                        block_Tap(blockMatrix[block.Row - 1, block.Column + 1], e);
                        block_Tap(blockMatrix[block.Row, block.Column - 1], e);
                        block_Tap(blockMatrix[block.Row, block.Column + 1], e);
                        block_Tap(blockMatrix[block.Row + 1, block.Column - 1], e);
                        block_Tap(blockMatrix[block.Row + 1, block.Column], e);
                        block_Tap(blockMatrix[block.Row + 1, block.Column + 1], e);
                    }

                    // 设置失败
                    if (value == 9)
                    {
                        context.IsLosing = true;
                        SystemMethod.Vibrate(500);

                        return;
                    }

                    // 胜利判断
                    context.BlockLeftCount--;

                    if (context.IsWin)
                    {
                        LocalTop tops = new LocalTop();

                        TopItem item = new TopItem
                                           {
                                               Difficulty = App.Context.Difficulty,
                                               Score = App.Context.ShowTime,
                                               CreateDate = DateTime.Now,
                                           };

                        tops.AddToTop(item);
                    }
                });
        }

        private void FlagBtn_Click(object sender, RoutedEventArgs e)
        {
            this.Dispatcher.BeginInvoke(() =>{context.IsFlaging = !context.IsFlaging;});
        }

        protected override void OnBackKeyPress(System.ComponentModel.CancelEventArgs e)
        {
            if (popStartGame.IsOpen)
            {
                popStartGame.IsOpen = false;
                e.Cancel = true;
                return;
            }

            if(popWin.IsOpen)
            {
                popWin.IsOpen = false;
                e.Cancel = true;
                return;
            }

            var msgRst = MessageBox.Show("确实要退出吗？", "退出游戏", MessageBoxButton.OKCancel);

            if (msgRst == MessageBoxResult.Cancel)
            {
                e.Cancel = true;
            }

            // Release Timer
            context.StopTimer();
        }
    }
}